char 陣列前幾天我們用陣列存放一串數字。那麼,一串文字又是怎麼存的呢?在 C 語言中,字串(string)可以放在 char 陣列裡,最後用特殊的結束標記 '\0'(空字元)表示文字到此為止。先看一個只有英文字母的例子:
char word[4] = "cat";
這個陣列的內容可以想成:
索引: 0 1 2 3
內容: 'c' 'a' 't' '\0'
"cat" 看起來只有三個字母,卻需要四個 char 的空間。因為 '\0' 告訴處理字串的函式:「文字到這裡結束。」如果少了這個標記,這些函式就無法只靠陣列本身判斷字串在哪裡結束,可能讀到陣列範圍以外。'c' 是單一字元;"c" 則是包含 'c' 與 '\0' 的字串,兩者不同。
C 語言要使用下面這些函式,先在程式開頭寫 #include <string.h>:
strlen(word):看字串有多長,不計算最後的 \0。strcpy(copy, word):把 word 複製到 copy。strcat(word, "fish"):把 "fish" 接在 word 後面。strcmp(word, "catfish"):比較兩段文字;相同時回傳 0。下面用一個完整範例觀察這些操作:
#include <stdio.h>
#include <string.h>
int main(void) {
char word[16] = "cat";
char copy[16];
printf("原本的字串:%s,長度:%zu\n", word, strlen(word));
strcpy(copy, word);
printf("複製後:%s\n", copy);
strcat(word, "fish");
printf("連接後:%s\n", word);
if (strcmp(word, "catfish") == 0) {
printf("兩個字串的內容相同\n");
}
return 0;
}
程式會輸出:
原本的字串:cat,長度:3
複製後:cat
連接後:catfish
兩個字串的內容相同
這裡的 strlen(word) 得到 3,指的是目前字串的長度,不是陣列的容量 16。複製後,copy 是 "cat";連接後,word 變成 "catfish",所以比較結果是相同。比較字串內容要用 strcmp(),不能用 ==;== 比較的是位址。
複製或連接時,目的陣列要放得下完整字串和最後的 \0。例如 "catfish" 要占 8 個位置;範例中的 word[16] 放得下。strcpy() 和 strcat() 不會替我們檢查容量,字串太長就可能越界。
補充:一個 char 占用一個位元組;在這個英文範例中,一個字母剛好占一個 char。但 UTF-8 中文字通常需要多個位元組,所以 strlen() 的結果不能直接當成中文字數。
一維陣列只需要一個索引,例如 scores[2]。如果資料有「列」和「欄」,就可以用二維陣列來表示。下面這個陣列有兩列,每列放三個數字:
int numbers[2][3] = {
{10, 20, 30},
{40, 50, 60}
};

圖中的 row 是列,col 是欄。[2][3] 代表 2 列、每列 3 欄,共有 2 × 3 = 6 個元素。索引都是從 0 開始,讀取時先指定 row,再指定 col。所以 numbers[1][2] 位於 row = 1、col = 2,也就是圖中右下角的 60。
要依照圖中的順序印出全部元素,可以使用兩層迴圈:外層選一列,內層依序走過該列的三個欄位。
#include <stdio.h>
int main(void) {
int numbers[2][3] = {
{10, 20, 30},
{40, 50, 60}
};
for (int row = 0; row < 2; row++) {
for (int col = 0; col < 3; col++) {
printf("%d ", numbers[row][col]);
}
printf("\n");
}
return 0;
}
外層迴圈第一次執行時,row 是 0,內層依序印出 10、20、30;第二次 row 是 1,印出 40、50、60。因此輸出為:
10 20 30
40 50 60
圖上的表格只是方便理解的畫法,不代表記憶體真的分成兩排。C 語言會先連續存放第 0 列的 10、20、30,再接著存放第 1 列的 40、50、60。這種一列接著一列的排列方式稱為「列優先」(row-major order)。
陣列不只可以有兩維。三維陣列可以先想成「好幾張二維表格疊在一起」:
int pages[2][3][4]; // 2 頁,每頁 3 列,每列 4 欄
int books[2][3][4][5]; // 2 本書,每本 3 頁,每頁 4 列,每列 5 欄

圖中有兩層 page,每層都是 3 個 row、4 個 col,總共有 2 × 3 × 4 = 24 個元素。像 pages[1][2][3],就是選擇 page = 1、row = 2、col = 3,也就是日常說的第 2 層、第 3 列、第 4 欄;每個索引都從 0 開始。
到了四維,就很難再用我們熟悉的立體空間,把四個方向同時畫出來。但這不代表四維陣列無法表示:可以像 books 一樣,想成「2 本書,每本 3 頁,每頁 4 列,每列 5 欄」,或一次只畫出其中一本、其中一頁。維度增加,重點不是想像更高維的空間,而是知道每多一維,就多一個索引來選擇資料。這些圖像只是理解上的比喻;實際記憶體仍是連續排列的。
字串讓我們看到 char 陣列如何存放文字,以及結束標記 '\0' 為什麼重要;多維陣列則讓資料多了列、欄等索引,方便表示表格或更深的分組。先熟練二維陣列的索引與走訪,三維、四維只要掌握「每多一維,就多一個索引」即可。
今日重點:
char 陣列中,並以 \0 標示結尾。strlen()、strcpy()、strcat() 和 strcmp() 可處理常見的字串操作;複製與連接時要注意容量。[列][欄] 存取元素,通常以兩層迴圈走訪。現在我們知道,陣列裡的資料總是緊挨著排隊;如果不排在一起,還能找到下一筆資料嗎?
下一篇就來認識鏈結串列,看看節點如何靠指標互相「牽線」,再親手串起一條從 head 出發、最後走到 NULL 的單向鏈結串列。